import type { IProps } from 'ahooks/lib/useWhyDidYouUpdate'
import { useEffect, useRef, useState } from 'react'
import styles from './index.module.less'
import { Image, Toast } from 'antd-mobile'
import iconBack from '@/resource/rainbow/icon_back.png'
import iconTuichuquanping from '@/resource/rainbow/icon_tuichuquanping.png'
import iconQuanping from '@/resource/rainbow/icon_quanping.png'
import iconVideo from '@/resource/rainbow/icon_video.png'
import iconReset from '@/resource/rainbow/icon_reset.png'
import iconTijiao from '@/resource/rainbow/icon_tijiao.png'
import { info, save, syncTrainData, uploadFile } from '../../api'
import type { GenerateRainbowRefType, LineDataType, LineDetailType, RainbowDataType, SettingType } from '../../interface'
import { transformChart, transformData } from './util'
import GenerateRainbow from '@/components/GenerateRainbow'
import { dataURLtoFile } from '@/utils'
import ConfirmModal from '@/pages/careerrainbow/components/ConfirmModal'
import { history } from 'umi'
import { getLocalStorage } from '@/storage'

export default function Chart(props: IProps) {
    const { id } = (history.location.query as Record<string, string>) || {}
    /** 1-学员，2-讲师 */
    const identityType = getLocalStorage('IDENTITY_TYPE')
    const generateRef = useRef<GenerateRainbowRefType>()
    // 画布大小
    let [canvasSize, setCanvasSize] = useState({ width: 0, height: 0 })

    // 线条数据
    let [postList, setPostList] = useState<LineDataType[]>([
        {
            post: '子女',
            color: '#9B92FF',
            data: [],
        },
        {
            post: '学生',
            color: '#829DFF',
            data: [],
        },
        {
            post: '休闲者',
            color: '#8CE2FB',
            data: [],
        },
        {
            post: '公民',
            color: '#A4FABA',
            data: [],
        },
        {
            post: '工作者',
            color: '#DDD877',
            data: [],
        },
        {
            post: '持家者',
            color: '#FF7EA5',
            data: [],
        },
    ])
    // 弹窗是否打开
    const [modalOpen, setModalOpen] = useState<boolean>(false)
    // 弹窗类型1-清空，2-已生成，3-同步，4-返回
    const [modalType, setModalType] = useState<string>('1')
    // 是否编辑过彩虹图
    const [isEdit, setIsEdit] = useState(false)
    // 全屏状态
    let [full, setFull] = useState(false)
    // 鼠标悬停详细信息
    let [detailData, setDetailData] = useState<LineDetailType>({ x: 0, y: 0, min: 0, max: 0, score: 0 })

    // 阶段提示文案信息
    const stageData = [
        { title: '成长阶段', x: 211, y: 772 },
        { title: '探索阶段', x: 280, y: 553 },
        { title: '建立阶段', x: 536, y: 278 },
        { title: '维持阶段', x: 920, y: 174 },
        { title: '退出阶段', x: 1468, y: 420 },
    ]

    // 最小线条半径
    let radius = 240
    // 线条间隔
    let radiusDelta = 60
    // 年龄平分角度
    let parts = 1 / 100
    // 画线条的宽度
    let activeLineWidth = 16
    // 线条的宽度
    let lineWidth = 2
    // 当前鼠标选中的线条
    let currentArc = {
        index: 0,
        score: 0,
        dataIndex: 0,
        radius: 0,
        direction: 0,
    }
    // 页面大小
    let [containerSize, setContainerSize] = useState({ height: 0, top: 0 })

    // 获取字体大小
    const getFontSize = (fontSize: number): string => {
        return `${(fontSize / 1920) * 100}vw`
    }

    const getVw = (size: number): number => {
        return (size / 1920) * canvasSize.width
    }

    const getVh = (size: number): number => {
        return (size / 1080) * canvasSize.height
    }

    const getRadius = (): number => {
        return getVw(radius)
    }

    const getRadiusDelta = (): number => {
        return getVw(radiusDelta)
    }

    const getActiveLineWidth = (): number => {
        return getVw(activeLineWidth)
    }

    const getCircleRadius = (circle: number): number => {
        return getVw(radius) + getVw(radiusDelta) * circle
    }

    // 设计稿宽高比
    const getAspectRatio = (): number => {
        // 就是9:16
        return 1080 / 1920
    }

    // 绘画更新
    const draw = () => {
        const cvEl = document.getElementById('cv') as HTMLCanvasElement
        if (cvEl) {
            // 1.
            const ctx = cvEl.getContext('2d') as CanvasRenderingContext2D
            let dpr = window.devicePixelRatio
            const w = cvEl.clientWidth
            const h = cvEl.clientHeight
            if (dpr) {
                cvEl.width = w * dpr
                cvEl.height = h * dpr
                ctx.scale(dpr, dpr)
            }
            // 清除画布
            ctx.clearRect(0, 0, w, h)
            let paintX = w / 2
            let paintY = getVh(1080) - getVh(174)
            for (let i = 0; i < postList.length; i++) {
                ctx.strokeStyle = postList[i].color
                ctx.lineWidth = lineWidth
                ctx.lineCap = 'round'
                ctx.beginPath()
                const lineRadius = getRadius() + getRadiusDelta() * i
                ctx.arc(paintX, paintY, lineRadius, 0, Math.PI, true)
                ctx.stroke()
                // 画线条
                const data = postList[i].data
                for (let j = 0; j < data.length; j++) {
                    ctx.strokeStyle = postList[i].color
                    ctx.lineWidth = (activeLineWidth / 1080) * h
                    ctx.lineCap = 'butt'
                    ctx.beginPath()

                    if ((data[j].minAngle === 0 && data[j].maxAngle === 0) || currentArc.radius === 0) {
                        let end = 1 + parts * data[j].min
                        let endAngle = Math.PI * end
                        if (endAngle < Math.PI) {
                            endAngle = Math.PI
                        }
                        data[j].minAngle = endAngle
                        let start = 1 + parts * data[j].max
                        let startAngle = Math.PI * start
                        if (startAngle > 2 * Math.PI) {
                            startAngle = 2 * Math.PI
                        }
                        data[j].maxAngle = startAngle
                    }

                    let dataLineRadius = getVw(radius) + getVw(radiusDelta) * i + getActiveLineWidth() / 2 + getActiveLineWidth() * (data[j].score - 1)
                    ctx.arc(paintX, paintY, dataLineRadius, data[j].maxAngle, data[j].minAngle, true)
                    ctx.stroke()
                }

                // 线条标题
                if (postList[i].post) {
                    ctx.fillStyle = '#fafbfb'
                    ctx.textAlign = 'center'
                    ctx.font = `${getFontSize(20)} PingFangSC`
                    ctx.fillText(postList[i].post, paintX, paintY - lineRadius - getActiveLineWidth())
                }
            }

            ctx.strokeStyle = '#ff7ea5'
            ctx.lineWidth = lineWidth
            ctx.lineCap = 'round'
            ctx.beginPath()
            ctx.arc(paintX, paintY, getCircleRadius(6), 0, Math.PI, true)
            ctx.stroke()

            ctx.strokeStyle = '#ffe496'
            ctx.lineWidth = lineWidth
            ctx.lineCap = 'round'
            ctx.beginPath()
            let circle7Radius = getRadius() + getRadiusDelta() * 7
            let circle7Angle = getVh(80) / circle7Radius / Math.PI
            ctx.arc(paintX, paintY, getRadius() + getRadiusDelta() * 7, -circle7Angle, Math.PI + circle7Angle, true)
            ctx.stroke()

            ctx.strokeStyle = '#ffe496'
            ctx.lineWidth = lineWidth
            ctx.lineCap = 'round'
            ctx.beginPath()
            let circle8Radius = getRadius() + getRadiusDelta() * 8
            let circle8Angle = getVh(80) / circle8Radius / Math.PI
            ctx.arc(paintX, paintY, circle8Radius, -circle8Angle, Math.PI + circle8Angle, true)
            ctx.stroke()

            // 更新页面相关标题
            ctx.fillStyle = '#ffffff'
            ctx.textAlign = 'center'
            ctx.font = `${getFontSize(28)} PingFangSC`
            ctx.fillText('个人决定因素', paintX, paintY - getVh(80))

            ctx.fillStyle = '#ffffff'
            ctx.textAlign = 'left'
            ctx.font = `${getFontSize(18)} PingFangSC`
            ctx.fillText('心理的', paintX + getVw(8), paintY - getVh(47))

            ctx.fillStyle = '#ffffff'
            ctx.textAlign = 'right'
            ctx.font = `${getFontSize(18)} PingFangSC`
            ctx.fillText('生物的', paintX - getVw(8), paintY - getVh(47))

            ctx.fillStyle = '#ffffff'
            ctx.textAlign = 'left'
            ctx.font = `${getFontSize(28)} PingFangSC`
            ctx.fillText('环境决定因素', getVw(1392), getVh(226))

            ctx.fillStyle = '#ffffff'
            ctx.textAlign = 'left'
            ctx.font = `${getFontSize(18)} PingFangSC`
            ctx.fillText('历史的 社会经济的', getVw(1392), getVh(274))

            let liveTitleRadius = getRadius() + getRadiusDelta() * 6
            ctx.fillStyle = '#FED04B'
            ctx.textAlign = 'right'
            ctx.font = `${getFontSize(20)} PingFangSC`
            ctx.fillText('生命阶段与年龄', w / 2 - liveTitleRadius - getVw(20), paintY)
            ctx.fillStyle = '#FED04B'
            ctx.textAlign = 'left'
            ctx.font = `${getFontSize(20)} PingFangSC`
            ctx.fillText('年龄与生命阶段', w / 2 + liveTitleRadius + getVw(20), paintY)

            for (let k = 0; k < 20; k++) {
                ctx.fillStyle = '#FED04B'
                ctx.textAlign = 'center'
                ctx.font = `${getFontSize(20)} PingFangSC`
                let topHeight = getVh(1080) - getVh(174)
                let ageLineRadius = getRadius() + getRadiusDelta() * 6 + getVw(20)
                let num = (Math.PI / 20) * k
                let numY = Math.sin(num) * ageLineRadius
                let numX = Math.cos(num) * ageLineRadius
                if (k > 0) {
                    ctx.fillText(`${(20 - k) * 5}`, w / 2 + numX, topHeight - numY)
                }
            }

            // 阶段文案
            for (let m = 0; m < stageData.length; m++) {
                const stageDatum = stageData[m]
                ctx.fillStyle = '#FFA175'
                ctx.textAlign = 'left'
                ctx.font = `${getFontSize(20)}`
                let x = getVw(stageDatum.x)
                let y = getVh(stageDatum.y + 21)
                ctx.clearRect(x - getVw(4), y - getVw(24), getVw(88), getVh(36))
                ctx.fillText(stageDatum.title, x, y)
            }

            // 更新鼠标悬停提示信息
            if (detailData.x > 0 && detailData.y > 0) {
                ctx.save()
                ctx.fillStyle = '#FFFFFF'
                ctx.shadowColor = '#2B2626'
                ctx.shadowBlur = getVw(42)
                ctx.fillRect(detailData.x, detailData.y - getVh(40), getVw(158), getVh(40))
                ctx.restore()
                ctx.fillStyle = '#333333'
                ctx.textAlign = 'left'
                ctx.font = `${getFontSize(18)} PingFangSC`
                if (detailData.min === detailData.max) {
                    ctx.fillText(`${detailData.min}岁 ${detailData.score}分`, detailData.x + getVw(12), detailData.y - getVh(11))
                } else {
                    ctx.fillText(`${detailData.min}岁-${detailData.max}岁 ${detailData.score}分`, detailData.x + getVw(12), detailData.y - getVh(11))
                }
            }
        }
    }

    // 初始化
    const init = () => {
        const cvContainer = document.getElementById('cv_container')
        if (!cvContainer) {
            return
        }
        const aspectRatio = getAspectRatio()
        canvasSize = {
            width: cvContainer.clientWidth,
            height: cvContainer.clientWidth * aspectRatio,
        }
        containerSize = {
            top: (cvContainer.clientHeight - canvasSize.height) / 2,
            height: cvContainer.clientHeight,
        }
        setContainerSize(containerSize)
        setCanvasSize(canvasSize)
        window.requestAnimationFrame(draw)
    }

    // 请求接口获取彩虹图数据
    const fetch = () => {
        info().then(res => {
            const resData = res.data.map((item: RainbowDataType) => {
                const settings = item.settings?.map(i => {
                    return {
                        ...i,
                        // 投入程度改为最大是3
                        grade: Number(i.grade) > 3 ? 3 : Number(i.grade),
                    }
                })
                return {
                    ...item,
                    settings,
                }
            })
            let data = transformChart(resData)
            for (let i = 0; i < data.length; i++) {
                for (let j = 0; j < postList.length; j++) {
                    if (postList[j].post === data[i].name) {
                        postList[j] = {
                            post: data[i].name,
                            color: postList[j].color,
                            data: data[i].settings.map((val: SettingType) => {
                                return {
                                    min: parseFloat(val.age_start),
                                    max: parseFloat(val.age_end),
                                    minAngle: 0,
                                    maxAngle: 0,
                                    score: parseFloat(val.grade as string),
                                }
                            }),
                        }
                    }
                }
            }
            setPostList(postList)
            window.requestAnimationFrame(draw)
        })
    }

    useEffect(() => {
        init()
        window.onresize = init
        fetch()
        const cvEl = document.getElementById('cv')
        if (cvEl) {
            // 计算鼠标悬停显示的详细信息数据
            const showDetail = (e: MouseEvent) => {
                detailData = { x: 0, y: 0, min: 0, max: 0, score: 0 }
                setDetailData(detailData)
                if (currentArc.radius > 0) {
                    let temp = postList[currentArc.index].data[currentArc.dataIndex]
                    if (temp) {
                        detailData = {
                            x: e.clientX,
                            y: e.clientY - containerSize.top,
                            min: temp.min,
                            max: temp.max,
                            score: temp.score,
                        }
                        setDetailData(detailData)
                    }
                    return
                }
                let x = e.clientX - getVw(960)
                let y = containerSize.height - getVh(174) - containerSize.top - e.clientY
                let r = Math.sqrt(x * x + y * y)
                let currentAngle = 0
                if (x > 0) {
                    currentAngle = Math.PI - Math.asin(y / r) + Math.PI
                } else {
                    currentAngle = Math.asin(y / r) + Math.PI
                }
                const temp = { index: 0, dataIndex: 0, radius: 0, direction: 0, score: 0, min: 0, max: 0 }
                for (let i = 0; i < 6; i++) {
                    if (temp.radius > 0) {
                        break
                    }
                    let dataList = postList[i].data
                    dataList.sort((a, b) => {
                        if (a.min === b.min) {
                            return a.max - b.max
                        }
                        return a.min - b.min
                    })
                    let score = 0
                    let currentJ = null
                    let ifLineRadiusMin = getRadius() + getRadiusDelta() * i
                    let ifLineRadiusMax2 = getRadius() + getRadiusDelta() * i + getActiveLineWidth() * 3
                    for (let j = 0; j < dataList.length; j++) {
                        const dataListElement = dataList[j]
                        let lineRadius = getRadius() + getRadiusDelta() * i + getActiveLineWidth() + getActiveLineWidth() * (dataListElement.score - 1)
                        if (currentAngle >= dataListElement.minAngle && currentAngle <= dataListElement.maxAngle) {
                            if ((score === 0 || score < dataListElement.score) && r >= ifLineRadiusMin && r <= ifLineRadiusMax2) {
                                score = dataListElement.score
                                currentJ = dataListElement
                                temp.radius = lineRadius
                            }
                        }
                    }
                    if (score === 0) {
                        continue
                    }
                    let clearList = []
                    for (let j = 0; j < dataList.length; j++) {
                        const dataListElement = dataList[j]
                        if (dataListElement.score === score + 1) {
                            clearList.push(dataList[j])
                        }
                    }

                    let tempMin = currentJ?.min as number
                    let tempMax = currentJ?.max as number

                    for (let j = 0; j < clearList.length; j++) {
                        const dataListElement = clearList[j]
                        if ((currentJ?.min as number) <= dataListElement.min && (currentJ?.max as number) >= dataListElement.max) {
                            if (dataListElement.maxAngle > currentAngle && tempMax > dataListElement.min - 1) {
                                tempMax = dataListElement.min - 1
                            }
                            if (dataListElement.minAngle < currentAngle && tempMin < dataListElement.max + 1) {
                                tempMin = dataListElement.max + 1
                            }
                        }
                    }

                    let ifLineRadiusMax = getRadius() + getRadiusDelta() * i + getActiveLineWidth() + getActiveLineWidth() * (score - 1)
                    if (ifLineRadiusMin <= r && ifLineRadiusMax >= r) {
                        temp.min = tempMin
                        temp.max = tempMax
                        temp.score = score
                    } else {
                        break
                    }
                }
                if (temp.radius === 0) {
                    window.requestAnimationFrame(draw)
                    return
                }
                if (temp.score === 0) {
                    window.requestAnimationFrame(draw)
                    return
                }
                detailData = {
                    x: e.clientX,
                    y: e.clientY - containerSize.top,
                    min: temp.min,
                    max: temp.max,
                    score: temp.score,
                }
                setDetailData(detailData)
                window.requestAnimationFrame(draw)
            }

            // 监听鼠标移动
            cvEl.addEventListener('mousemove', e => {
                showDetail(e)
                if (currentArc.radius > 0) {
                    let y = containerSize.height - getVh(174) - containerSize.top - e.clientY
                    let x = e.clientX - getVw(960)
                    let num = 0
                    num = Math.asin(y / currentArc.radius)
                    if (num >= 1.2 && num <= 1.8) {
                        num = Math.acos(Math.abs(x) / currentArc.radius)
                    }
                    if (Number.isNaN(num)) {
                        return
                    }
                    let datum = null
                    if (currentArc.direction === 0) {
                        datum = { min: 0, max: 0, minAngle: 0, maxAngle: 0, score: currentArc.score }
                        let newAngle = 0
                        if (num < parts) {
                            num = 0
                        }
                        if (e.clientX > getVw(960)) {
                            newAngle = Math.PI - num + Math.PI
                        } else {
                            newAngle = Math.PI + num
                        }
                        if (newAngle > 2 * Math.PI) {
                            newAngle = 2 * Math.PI
                        }
                        if (newAngle < Math.PI) {
                            newAngle = Math.PI
                            datum.min = 0
                        }
                        datum.maxAngle = newAngle
                        datum.minAngle = newAngle
                        postList[currentArc.index].data.push(datum)
                        currentArc.dataIndex = postList[currentArc.index].data.length - 1
                    } else {
                        datum = postList[currentArc.index].data[currentArc.dataIndex]
                    }
                    if (!datum) {
                        return
                    }
                    let blank = datum.min === 0 && datum.max === 0
                    if (currentArc.direction === 1) {
                        let newMaxAngle = 0
                        if (e.clientX > getVw(960)) {
                            newMaxAngle = Math.PI - num + Math.PI
                        } else {
                            newMaxAngle = Math.PI + num
                        }
                        if (newMaxAngle > 2 * Math.PI) {
                            newMaxAngle = 2 * Math.PI
                        }
                        datum.maxAngle = newMaxAngle
                        if (datum.maxAngle < datum.minAngle) {
                            let temp = datum.minAngle
                            datum.minAngle = datum.maxAngle
                            datum.maxAngle = temp
                            currentArc.direction = 2
                        }
                    }

                    if (currentArc.direction === 2) {
                        let newMinAngle = 0
                        if (e.clientX > getVw(960)) {
                            newMinAngle = Math.PI - num + Math.PI
                        } else {
                            newMinAngle = Math.PI + num
                        }
                        if (newMinAngle < Math.PI) {
                            newMinAngle = Math.PI
                        }
                        datum.minAngle = newMinAngle
                        if (datum.maxAngle < datum.minAngle) {
                            let temp = datum.minAngle
                            datum.minAngle = datum.maxAngle
                            datum.maxAngle = temp
                            currentArc.direction = 1
                        }
                    }
                    if (blank) {
                        datum.minAngle = datum.maxAngle
                    }
                    let tempMin = (datum.minAngle - Math.PI) / (Math.PI * parts)
                    if (tempMin < 1) {
                        datum.min = 0
                        datum.minAngle = Math.PI
                    } else {
                        datum.min = Math.round(tempMin)
                    }
                    datum.max = Math.round((datum.maxAngle - Math.PI) / (Math.PI * parts))

                    if (currentArc.direction === 0) {
                        currentArc.direction = 1
                    }
                    setPostList(postList)
                    window.requestAnimationFrame(draw)
                }
            })

            // 监听释放鼠标
            cvEl.addEventListener('mouseup', e => {
                for (let i = 0; i < postList.length; i++) {
                    let dataList = postList[i].data
                    if (dataList) {
                        let list = []
                        let list1 = []
                        let list2 = []
                        let list3 = []
                        for (let j = 0; j < dataList.length; j++) {
                            const datum = dataList[j]
                            if (datum.max > datum.min) {
                                if (datum.score === 3) {
                                    list3.push(datum)
                                }
                                if (datum.score === 2) {
                                    list2.push(datum)
                                }
                                if (datum.score === 1) {
                                    list1.push(datum)
                                }
                            }
                        }

                        for (let j = 0; j < list3.length; j++) {
                            let datum3 = list3[j]
                            let center3 = datum3.min + (datum3.max - datum3.min) / 2
                            let datum2 = null
                            for (let k = 0; k < list2.length; k++) {
                                let temp = list2[k]
                                if (temp) {
                                    let center2 = temp.min + (temp.max - temp.min) / 2
                                    if (center3 === center2) {
                                        datum2 = temp
                                    }
                                }
                            }
                            if (!datum2) {
                                datum2 = {
                                    min: datum3.min,
                                    max: datum3.max,
                                    minAngle: datum3.minAngle,
                                    maxAngle: datum3.maxAngle,
                                    score: 2,
                                }
                                list2.push(datum2)
                                dataList.push(datum2)
                            }
                        }
                        for (let j = 0; j < list2.length; j++) {
                            let datum2 = list2[j]
                            let center2 = datum2.min + (datum2.max - datum2.min) / 2
                            let datum1 = null
                            for (let l = 0; l < list1.length; l++) {
                                let temp1 = list1[l]
                                if (temp1) {
                                    let center1 = temp1.min + (temp1.max - temp1.min) / 2
                                    if (center2 === center1) {
                                        datum1 = temp1
                                    }
                                }
                            }
                            if (!datum1) {
                                datum1 = {
                                    min: datum2.min,
                                    max: datum2.max,
                                    minAngle: datum2.minAngle,
                                    maxAngle: datum2.maxAngle,
                                    score: 1,
                                }
                                dataList.push(datum1)
                                list1.push(datum1)
                            }
                        }
                        let newList1 = list1.sort((a, b) => {
                            return a.min - b.min
                        })
                        let newList2 = list2.sort((a, b) => {
                            return a.min - b.min
                        })
                        let newList3 = list3.sort((a, b) => {
                            return a.min - b.min
                        })
                        let mergeList1 = []
                        for (let j = 0; j < newList1.length; j++) {
                            const currentItem = newList1[j]
                            if (j === 0) {
                                mergeList1.push(currentItem)
                            } else {
                                const mergeItem = mergeList1[mergeList1.length - 1]
                                if (currentItem.min >= mergeItem.min && currentItem.min <= mergeItem.max) {
                                    if (currentItem.max > mergeItem.max) {
                                        mergeItem.max = currentItem.max
                                        mergeItem.maxAngle = currentItem.maxAngle
                                    }
                                } else {
                                    mergeList1.push(currentItem)
                                }
                            }
                        }
                        let mergeList2 = []
                        for (let j = 0; j < newList2.length; j++) {
                            const currentItem = newList2[j]
                            if (j === 0) {
                                mergeList2.push(currentItem)
                            } else {
                                const mergeItem = mergeList2[mergeList2.length - 1]
                                if (currentItem.min >= mergeItem.min && currentItem.min <= mergeItem.max) {
                                    if (currentItem.max > mergeItem.max) {
                                        mergeItem.max = currentItem.max
                                        mergeItem.maxAngle = currentItem.maxAngle
                                    }
                                } else {
                                    mergeList2.push(currentItem)
                                }
                            }
                        }
                        let mergeList3 = []
                        for (let j = 0; j < newList3.length; j++) {
                            const currentItem = newList3[j]
                            if (j === 0) {
                                mergeList3.push(currentItem)
                            } else {
                                const mergeItem = mergeList3[mergeList3.length - 1]
                                if (currentItem.min >= mergeItem.min && currentItem.min <= mergeItem.max) {
                                    if (currentItem.max > mergeItem.max) {
                                        mergeItem.max = currentItem.max
                                        mergeItem.maxAngle = currentItem.maxAngle
                                    }
                                } else {
                                    mergeList3.push(currentItem)
                                }
                            }
                        }
                        list.push(...mergeList1)
                        list.push(...mergeList2)
                        list.push(...mergeList3)
                        postList[i].data = list
                    }
                }
                setPostList(postList)
                window.requestAnimationFrame(draw)
                currentArc = { index: -1, dataIndex: -1, radius: 0, direction: 0, score: 0 }
            })

            // 监听按下鼠标
            cvEl.addEventListener('mousedown', e => {
                setIsEdit(true)
                let x = e.clientX - getVw(960)
                let y = containerSize.height - getVh(174) - containerSize.top - e.clientY
                let r = Math.sqrt(x * x + y * y)
                currentArc = { index: 0, dataIndex: 0, radius: 0, direction: 0, score: 0 }
                let ok = false
                for (let i = 0; i < 6; i++) {
                    if (ok) {
                        break
                    }
                    let dataList = postList[i].data
                    for (let j = 0; j < 3; j++) {
                        // 线条的高度
                        let lineRadius = getRadius() + getRadiusDelta() * i + getActiveLineWidth() + getActiveLineWidth() * j
                        if (lineRadius >= r && r > lineRadius - getActiveLineWidth()) {
                            currentArc.index = i
                            currentArc.score = j + 1
                            currentArc.radius = lineRadius
                            for (let k = 0; k < dataList.length; k++) {
                                let datum = dataList[k]
                                if (datum && datum.score === currentArc.score) {
                                    let currentAngle = 0
                                    if (x > 0) {
                                        currentAngle = Math.PI - Math.asin(y / r) + Math.PI
                                    } else {
                                        currentAngle = Math.asin(y / r) + Math.PI
                                    }
                                    if (currentAngle >= datum.minAngle && currentAngle <= datum.maxAngle) {
                                        currentArc.dataIndex = k
                                        if (currentAngle - datum.minAngle > datum.maxAngle - currentAngle) {
                                            currentArc.direction = 1
                                        } else {
                                            currentArc.direction = 2
                                        }
                                        ok = true
                                    }
                                }
                            }

                            if (ok) {
                                break
                            }
                        }
                    }
                }
            })
        }
    }, [])
    /** 弹窗确认按钮 */
    const modalOk = () => {
        const skip_url = getLocalStorage('SKIP_URL')
        // 清空重置彩虹图
        if (modalType === '1') {
            for (let i = 0; i < postList.length; i++) {
                postList[i].data = []
            }
            window.requestAnimationFrame(draw)
            setPostList(postList)
        }
        // 已生成
        if (modalType === '2' && identityType === 1 && skip_url) {
            window.location.href = skip_url
        }
        // 同步
        if (modalType === '3') {
            syncTrainData(id).then(() => {
                if (identityType === 1 && skip_url) {
                    window.location.href = skip_url
                }
                Toast.show({ icon: 'success', content: '同步成功' })
            })
        }
        // 返回页面
        if (modalType === '4') {
            props.handleBack()
        }
        setModalOpen(false)
    }
    // 页面返回
    const handleBack = () => {
        if (props.handleBack && !isEdit) {
            props.handleBack()
        } else {
            setModalType('4')
            setModalOpen(true)
        }
    }

    // 控制全屏
    const handleToggleFullScreen = () => {
        const el = document.getElementById('cv_container')
        if (!el) {
            return
        }
        if (full) {
            full = false
            if (document.exitFullscreen) {
                document.exitFullscreen()
            } else if (document.webkitExitFullscreen) {
                document.webkitExitFullscreen()
            } else if (document.mozCancelFullScreen) {
                document.mozCancelFullScreen()
            } else if (document.msExitFullscreen) {
                document.msExitFullscreen()
            }
            setFull(full)
            return
        }
        full = true
        if (el.requestFullscreen) {
            el.requestFullscreen().then(r => {})
        } else if (el.mozRequestFullScreen) {
            el.mozRequestFullScreen().then(r => {})
        } else if (el.webkitRequestFullscreen) {
            el.webkitRequestFullscreen().then(r => {})
        } else if (el.msRequestFullscreen) {
            el.msRequestFullscreen().then(r => {})
        } else {
            full = false
        }
        setFull(full)
    }

    // 视频引导
    const handleGuide = () => {
        if (props.handleGuide) {
            props.handleGuide()
        }
    }

    // 重置彩虹图
    const handleReset = () => {
        setModalType('1')
        setModalOpen(true)
    }

    // 保存彩虹图数据
    const handleConfirm = () => {
        let params = { data: Array<RainbowDataType>() }
        for (let i = 0; i < postList.length; i++) {
            const datum = postList[i]
            if (!datum.data.length) {
                continue
            }
            let paramsData = {
                age_start: '0',
                age_end: '0',
                settings: Array<any>(),
                name: datum.post,
                sort: (i + 1).toString(),
            }
            let min = 100
            let max = 0
            const settings = datum.data
            for (let j = 0; j < settings.length; j++) {
                if (min > settings[j].min) {
                    min = settings[j].min
                }
                if (max === 0 || max < settings[j].max) {
                    max = settings[j].max
                }
                const settingsData = {
                    sort: (j + 1).toString(),
                    grade: settings[j].score.toString(),
                    age_start: settings[j].min.toString(),
                    age_end: settings[j].max.toString(),
                }
                paramsData.settings.push(settingsData)
            }
            paramsData.age_start = min.toString()
            paramsData.age_end = max.toString()
            params.data.push(paramsData)
        }
        const data = transformData(params.data)
        const base64Str = generateRef.current?.exportImage(JSON.parse(JSON.stringify(data)))
        if (base64Str) {
            const file = dataURLtoFile(base64Str, 'rainbow' + Math.floor(Math.random() * 10) + new Date().getTime() + '.png')
            uploadFile(file).then(res => {
                save(data, res.data.url).then(({ data: saveData }) => {
                    setModalType(saveData.is_first_view === '1' ? '2' : '3')
                    setModalOpen(true)
                    fetch()
                })
            })
        }
    }

    return (
        <>
            <div className={styles.container} id="cv_container">
                <div className={`${styles.button_back} ${styles.button_container}`} onClick={handleBack}>
                    <Image className={`${styles.button_icon} ${styles.button_icon_span}`} src={iconBack} />
                    <div>返回求职实训</div>
                </div>
                <div className={`${styles.full_button} ${styles.button_container}`} onClick={handleToggleFullScreen}>
                    <Image style={{ width: full ? 'auto' : 0 }} className={styles.button_icon} src={iconTuichuquanping} />
                    <Image style={{ width: !full ? 'auto' : 0 }} className={styles.button_icon} src={iconQuanping} />
                    <div className={styles.button_icon_span} />
                    <div>{full ? '退出全屏' : '全屏'}</div>
                </div>
                <div className={styles.float_button_group}>
                    {/* <div className={styles.float_button_item} onClick={handleGuide}>
                        <Image className={styles.float_button_icon} src={iconVideo} />
                        <div>操作视频</div>
                    </div> */}
                    <div className={styles.float_button_item} onClick={handleReset}>
                        <Image className={styles.float_button_icon} src={iconReset} />
                        <div>重置</div>
                    </div>
                    <div className={styles.float_button_item} onClick={handleConfirm}>
                        <Image className={styles.float_button_icon} src={iconTijiao} />
                        <div>提交</div>
                    </div>
                </div>
                <canvas id="cv" style={{ width: canvasSize.width, height: canvasSize.height, background: '#31374e' }} />
            </div>
            <GenerateRainbow ref={generateRef} />
            <ConfirmModal visible={modalOpen} type={modalType} handleCancel={() => setModalOpen(false)} handleOk={modalOk} />
        </>
    )
}
